package org.backend.canteenbackend.security;


import com.fasterxml.jackson.databind.ObjectMapper;
import jakarta.servlet.FilterChain;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.backend.canteenbackend.common.CommonResponse;
import org.backend.canteenbackend.util.GlobalExceptionHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.web.filter.OncePerRequestFilter;

import java.io.IOException;
import java.util.Collections;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

@Slf4j
@Component
public class JwtAuthFilter extends OncePerRequestFilter {
    @Autowired
    private JwtUtil jwtUtil;
    @Autowired
    private SecurityConfig securityConfig;

    private ObjectMapper objectMapper = new ObjectMapper();
    Logger logger= LoggerFactory.getLogger(GlobalExceptionHandler.class);

    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
            throws ServletException, IOException {

        String authHeader = request.getHeader("Authorization");
        String usernameFromToken="";
        String requestURI = request.getRequestURI();
        if(authHeader==null) {
            String[] permittedRoutes = securityConfig.getPermittedRoutes();
            boolean isPermitted = false;
            for (String route : permittedRoutes) {
                if (requestURI.startsWith(route)) {
                    isPermitted = true;
                    break;
                }
            }
            if (!isPermitted) {
            response.getWriter().write(objectMapper.writeValueAsString(CommonResponse.createForError("No Authorization")));
            return;}
        }
        if (authHeader != null && authHeader.startsWith("Bearer ")) {
            String token = authHeader.substring(7);
            if (!jwtUtil.validateToken(token)) {
                logger.error("Invalid JWT Token");
                response.getWriter().write(objectMapper.writeValueAsString(CommonResponse.createForError("Invalid JWT Token")));
                return;
            }

            UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(
                    jwtUtil.extractUsername(token), null, Collections.emptyList());
            usernameFromToken=jwtUtil.extractUsername(token);
            SecurityContextHolder.getContext().setAuthentication(authentication);
        }
        // 获取请求的URI
        // 定义正则表达式来匹配路径中的 username
        Pattern pattern = Pattern.compile("/information/([^/]+)");
        Matcher matcher = pattern.matcher(requestURI);

        if (matcher.find()) {
            String usernameFromPath = matcher.group(1);
            // 验证路径中的用户名与令牌中的用户名是否一致
            if (usernameFromToken != null && !usernameFromToken.equals(usernameFromPath)) {
                logger.error("Invalid JWT Token");
                response.getWriter().write(objectMapper.writeValueAsString(CommonResponse.createForError("Invalid JWT Token")));
                return;
            }
        }

        filterChain.doFilter(request, response);

    }
}
